﻿// Decompiled with JetBrains decompiler
// Type: DnProcessSimulateCommands.TCPFTracker.TCPFTrackCurveCreator
// Assembly: DnProcessSimulateCommands, Version=2402.0.0.890, Culture=neutral, PublicKeyToken=null
// MVID: A885D881-AEDF-447E-852A-6F13102E089C
// Assembly location: C:\Program Files\Tecnomatix_2402\eMPower\DotNetCommands\DnProcessSimulateCommands.dll

using System;
using System.Collections;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using Tecnomatix.Engineering;


namespace DnProcessSimulateCommands.TCPFTracker;

public class TCPFTrackCurveCreator
{
  private bool _lissenToSetAbsLocEvent;
  private bool _pause;
  private TxFrame _frame;
  private ITxLocatableObject _parent;
  private ITxGeometry _curve;
  private TxColor _curveColor = TxColor.TxColorWhite;
  private int _curveCounter;
  private ArrayList _points;
  private TxComponent _comp;
  private string _locatableObjectName;
  private TxObjectList _createdComponents;
  private List<ManipulatorExtend> _manipulators = new List<ManipulatorExtend>();
  private ManipulatorExtend _activeManipulator;

  public TCPFTrackCurveCreator() => this._createdComponents = new TxObjectList();

  public TxColor CurveColor
  {
    set
    {
      this.PauseRecording();
      this._curveColor = value;
      this.PauseRecording();
    }
    get => this._curveColor;
  }

  public TxComponent Component => this._comp;

  public bool Paused => this._pause;

  public TxObjectList CreatedComponents => this._createdComponents;

  public void StopRecording()
  {
    if (this._manipulators.Count > 0)
      this.CreateGeometries();
    if (this._curve != null)
      ((ITxObject) this._curve).Deleted -= new TxObject_DeletedEventHandler(this.OnObjectDeleted);
    if (TxComponent.op_Inequality(this._comp, (ITxObject) null))
      ((TxBaseGeometryCreationObject) this._comp).Deleted -= new TxObject_DeletedEventHandler(this.OnObjectDeleted);
    if (this._lissenToSetAbsLocEvent)
    {
      this._parent.AbsoluteLocationChanged -= new TxLocatableObject_AbsoluteLocationChangedEventHandler(this.OnLocationChanged);
      this._lissenToSetAbsLocEvent = false;
    }
    this._comp = (TxComponent) null;
    this._curveCounter = 0;
    this._curve = (ITxGeometry) null;
    this._pause = false;
    this._points = (ArrayList) null;
    this._activeManipulator = (ManipulatorExtend) null;
  }

  public void StartRecording(ITxLocatableObject trackedObject, TxFrame trackedFrame)
  {
    this._comp = (TxComponent) null;
    this._curveCounter = 0;
    this._curve = (ITxGeometry) null;
    this._pause = false;
    this._points = (ArrayList) null;
    this._activeManipulator = (ManipulatorExtend) null;
    this._frame = trackedFrame;
    this._locatableObjectName = ((ITxObject) trackedObject).Name;
    this._points = new ArrayList(20);
    this._points.Add((object) this._frame.AbsoluteLocation.Translation);
    this.SetObserverOnTCPFParentLink(trackedObject);
  }

  public void PauseRecording()
  {
    this._pause = !this._pause;
    if (this._pause)
    {
      if (this._manipulators.Count > 0)
        this.CreateGeometries();
      if (this._curve != null)
        ((ITxObject) this._curve).Deleted -= new TxObject_DeletedEventHandler(this.OnObjectDeleted);
      this._curve = (ITxGeometry) null;
      ++this._curveCounter;
      if (this._points == null)
        return;
      this._points.Clear();
    }
    else
      this._points.Add((object) this._frame.AbsoluteLocation.Translation);
  }

  private void SetObserverOnTCPFParentLink(ITxLocatableObject locatableObject)
  {
    ITxLocatableObject itxLocatableObject = (ITxLocatableObject) this._frame;
    for (TxTypeFilter txTypeFilter = new TxTypeFilter(typeof (TxKinematicLink)); itxLocatableObject != null && !txTypeFilter.DoesPassFilter((ITxObject) itxLocatableObject); itxLocatableObject = this._parent)
    {
      this._parent = itxLocatableObject.AttachmentParent;
      if (this._parent == null)
        this._parent = ((ITxObject) itxLocatableObject).Collection as ITxLocatableObject;
    }
    if (this._parent == null)
    {
      if (locatableObject is ITxDevice)
      {
        TxObjectList links = ((ITxDevice) locatableObject).Links;
        this._parent = (ITxLocatableObject) ((Collection<ITxObject>) links)[((Collection<ITxObject>) links).Count - 1];
      }
      else
        this._parent = locatableObject;
    }
    this._parent.AbsoluteLocationChanged += new TxLocatableObject_AbsoluteLocationChangedEventHandler(this.OnLocationChanged);
    this._lissenToSetAbsLocEvent = true;
  }

  private void CreateComponent()
  {
    TxLocalComponentCreationData componentCreationData = new TxLocalComponentCreationData();
    string str = this._locatableObjectName + "_TCP_track";
    ((TxObjectCreationData) componentCreationData).Name = TxApplication.ActiveDocument.PhysicalRoot.GetUniqueDisplayName(str);
    this._comp = TxApplication.ActiveDocument.PhysicalRoot.CreateLocalComponent(componentCreationData);
    ((Collection<ITxObject>) this._createdComponents).Add((ITxObject) this._comp);
    ((TxBaseGeometryCreationObject) this._comp).Deleted += new TxObject_DeletedEventHandler(this.OnObjectDeleted);
  }

  private void CreateCurve()
  {
    this._points.Add((object) this._frame.AbsoluteLocation.Translation);
    try
    {
      ITxGeometry itxGeometry = (ITxGeometry) null;
      if (this._points.Count == 2)
        itxGeometry = (ITxGeometry) ((TxBaseGeometryCreationObject) this._comp).CreateLine(new TxLineCreationData(this.CreateUniqueName())
        {
          StartPoint = (TxVector) this._points[0],
          EndPoint = (TxVector) this._points[1]
        });
      else if (this._points.Count > 2)
        itxGeometry = ((TxBaseGeometryCreationObject) this._comp).CreatePolylineAsGeometry(new TxPolylineCreationData(this.CreateUniqueName(), this._points));
      if (itxGeometry == null)
        return;
      this._curve = itxGeometry;
      ((ITxDisplayableObject) this._curve).Color = this._curveColor;
      ((ITxObject) this._curve).Deleted += new TxObject_DeletedEventHandler(this.OnObjectDeleted);
    }
    catch (Exception ex)
    {
    }
  }

  private string CreateUniqueName()
  {
    string uniqueName = this._locatableObjectName + "_TCP_track_curve";
    if (this._curveCounter > 0)
      uniqueName = uniqueName + "_" + this._curveCounter.ToString();
    return uniqueName;
  }

  private void DeleteCurve()
  {
    ((ITxObject) this._curve).Deleted -= new TxObject_DeletedEventHandler(this.OnObjectDeleted);
    ((ITxObject) this._curve).Delete();
    this._curve = (ITxGeometry) null;
  }

  private void OnLocationChanged(
    object sender,
    TxLocatableObject_AbsoluteLocationChangedEventArgs args)
  {
    if (this._pause)
      return;
    this._pause = true;
    if (TxComponent.op_Equality(this._comp, (ITxObject) null))
    {
      this.CreateComponent();
    }
    else
    {
      if (this._activeManipulator != null)
        this._activeManipulator = (ManipulatorExtend) null;
      int capacity = this._points.Capacity;
      if (this._points.Count == capacity)
        this._points.Capacity = capacity * 2;
    }
    this._points.Add((object) this._frame.AbsoluteLocation.Translation);
    this.CreateManipulator(this.CreateUniqueName());
    this._pause = false;
  }

  private void OnObjectDeleted(object sender, TxObject_DeletedEventArgs args)
  {
    if (TxComponent.op_Inequality(this._comp, (ITxObject) null) && ((ITxObject) sender).Id == ((TxBaseGeometryCreationObject) this._comp).Id)
    {
      ((TxBaseGeometryCreationObject) this._comp).Deleted -= new TxObject_DeletedEventHandler(this.OnObjectDeleted);
      this._comp = (TxComponent) null;
      this._curveCounter = 0;
    }
    else
    {
      if (this._curve == null || !(((ITxObject) sender).Id == ((ITxObject) this._curve).Id))
        return;
      ((ITxObject) this._curve).Deleted -= new TxObject_DeletedEventHandler(this.OnObjectDeleted);
      this._curve = (ITxGeometry) null;
      this._points.Clear();
      if (this._pause)
        return;
      this._points.Add((object) this._frame.AbsoluteLocation.Translation);
    }
  }

  private void CreateGeometries()
  {
    if (TxComponent.op_Equality(this._comp, (ITxObject) null) && this._manipulators.Count > 0)
      this.CreateComponent();
    foreach (ManipulatorExtend manipulator in this._manipulators)
    {
      try
      {
        ITxGeometry itxGeometry;
        if (manipulator.Points.Count == 2)
          itxGeometry = (ITxGeometry) ((TxBaseGeometryCreationObject) this._comp).CreateLine(new TxLineCreationData(manipulator.Name)
          {
            StartPoint = (TxVector) manipulator.Points[0],
            EndPoint = (TxVector) manipulator.Points[1]
          });
        else
          itxGeometry = ((TxBaseGeometryCreationObject) this._comp).CreatePolylineAsGeometry(new TxPolylineCreationData(manipulator.Name, manipulator.Points));
        if (itxGeometry != null)
          ((ITxDisplayableObject) itxGeometry).Color = manipulator.Color;
        if (this._curve != null)
          ((ITxObject) this._curve).Deleted -= new TxObject_DeletedEventHandler(this.OnObjectDeleted);
        this._curve = itxGeometry;
        if (this._curve != null)
          ((ITxObject) this._curve).Deleted += new TxObject_DeletedEventHandler(this.OnObjectDeleted);
      }
      catch (Exception ex)
      {
      }
      finally
      {
        manipulator.Manipulator.Delete();
      }
    }
    this._manipulators.Clear();
    this._activeManipulator = (ManipulatorExtend) null;
  }

  private void CreateManipulator(string name)
  {
    if (!this._manipulators.Contains(new ManipulatorExtend(name)))
    {
      TxManipulator manipulator = TxApplication.ActiveDocument.PhysicalRoot.CreateManipulator(new TxManipulatorCreationData(name, new TxTransformation()));
      this._manipulators.Add(new ManipulatorExtend(name, manipulator, this._points, this._curveColor));
    }
    int index1 = this._manipulators.IndexOf(new ManipulatorExtend(name));
    if (index1 < 0)
      return;
    ManipulatorExtend manipulator1 = this._manipulators[index1];
    manipulator1.Color = this._curveColor;
    manipulator1.Points = this._points;
    this._activeManipulator = manipulator1;
    this._activeManipulator.Manipulator.RemoveAllElements();
    for (int index2 = 1; index2 < this._points.Count; ++index2)
    {
      TxManipulatorElementData manipulatorElementData = (TxManipulatorElementData) new TxManipulatorLineElementData(new TxTransformation(), (TxVector) this._points[index2 - 1], (TxVector) this._points[index2]);
      manipulatorElementData.Color = this._curveColor;
      manipulatorElementData.AlwaysOnTop = false;
      this._activeManipulator.Manipulator.AddElement(manipulatorElementData);
    }
    this._activeManipulator.Manipulator.Display();
  }
}
